Chapter 1 Console Device This chapter describes how you do console (keyboard and screen) input and output on the Amiga. The console device acts like an enhanced ASCII terminal. It obeys many of the standard ANSI sequences as well as additional special sequences unique to the Amiga. 1.1. INTRODUCTION Console I/O is tied closely to the Amiga Intuition interface; a console must be tied to a window that is already opened. From the Window data structure, the console device determines how many characters it can display on a line and how many lines of text it can display in a window without clipping at any edge. You can open the console device many times, if you wish. The result of each open call is a new console unit. AmigaDOS and Intuition see to it that only one window is the currently active one, and its console, if any, is the only one (with a few excep- tions) that receives notification of input events, such as keys- trokes. Later in this chapter you'll see that other Intuition events can be sensed by the console device as well. NOTE: For this entire chapter the characters "" represent the Control Sequence Introducer. For output you may either use the two-character sequence "[" or the one-byte value $9B (hex). For input you will receive $9B's. 1.2. SYSTEM FUNCTIONS The various system functions, such as DoIO(), SendIO(), Abor- tIO(), CheckIO() and so on operate normally. The only caveats are that the CMD_WRITE may cause the caller to wait internally, even with SendIO(), and a task waiting on response from a console is at the user's whim. If a user never reselects that window, and the console response provides the only wakeup-call, that task may well sleep indefinitely. November 17, 1985 - 2 - 1.3. CONSOLE I/O The console device may be thought of as a kind of a terminal. You send a character stream to the console device. You also receive a character stream from the console device. These streams may be characters or special sequences. Console character screen output (as compared to console command sequence transmission) outputs all standard printable characters (character values hex 20 thru 7E and A0 thru FF) normally. Many control characters such as BACKSPACE and RETURN are translated into their exact ANSI equivalent actions. The line-feed charac- ter is a bit different, in that it can be translated into a new- line character. The net effect is that the cursor moves to the first column of the next line whenever a is displayed. This is set via the mode control sequences discussed under "Control Sequences for Screen Output". If you read from the console device, the keyboard inputs are preprocessed for you. You will get the ASCII characters such as "B". Most normal text gathering programs will read from the con- sole device in this manner. Special programs like word proces- sors and music keyboard programs will use raw input. Keys are converted via the keymap associated with the unit. The sections below deal with the following topics: o Setting up for console I/O (creating an I/O request structure) o Writing to the console to control its behavior o Reading from the console o Closing down a console device This section shows you how to set up for console I/O. 1.4. CREATING AN I/O REQUEST Console I/O, like other devices, requires that you create an I/O request message that you pass to the console device for process- ing. The message contains the command, as well as a data area. In the data area, for a write, there will be a pointer to the stream of information you wish to write to the console. For a read, this data pointer shows where the console is to copy the data it has for you. There is also a length field that says how many characters (maximum) are to be copied either from or to the console device. November 17, 1985 - 3 - Here is a program fragment that can be used to create the message block that you use for console communications. For writing to the console: struct IOStdReq *consoleWriteMsg; /* I/O request block pointer */ struct Port *consoleWritePort; /* a port at which to receive replies*/ consoleWritePort = CreatePort("mycon.write",0); if(consoleWritePort == 0) exit(100); /* error in createport */ consoleWriteMsg = CreateStdIO(consoleWritePort); if(consoleWriteMsg == 0) exit(200); /* error in createstdio */ For reading from the console: struct IOStdReq *consoleReadMsg; /* I/O request block pointer */ struct Port *consoleReadPort; /* a port at which to receive replies */ consoleReadPort = CreatePort("mycon.read",0); if(consoleReadPort == 0) exit(300); /* error in createport */ consoleReadMsg = CreateStdIO(consoleReadPort); if(consoleReadMsg == 0) exit(400); /* error in createstdio */ These fragments show two messages and ports being set up. You would use this if you want to have a read command continuously queued up while using a separate message with its associated port to send control command sequences to the console. In addition, if you want to queue up multiple commands to the console, you may wish to create multiple messages (but probably just one port for receiving replied messages from the device). 1.5. OPENING A CONSOLE DEVICE For other devices, you normally use OpenDevice() to pass an unin- itialized IORequest block to the device. For a console device, this is slightly different. You must have initialized two fields in the request block; namely, the data pointer and the length field. Here is a subroutine that can be used to open a console device (attach it to an existing window). It assumes that intuition.library is already open, a window has also been opened, and this new console is to be attached to the open window. November 17, 1985 - 4 - /* this function returns a value of 0 if the console * device opened correctly and a nonzero value (the error * returned from OpenDevice) if there was an error. */ OpenConsole(request,window) struct IOStdReq *request; struct Window *window; { /* Open a console device */ request->io_Data = (char *) window; request->io_Length = sizeof(*window); return(OpenDevice("console.device", 0, request, 0)); } To perform console I/O, you fill in fields of the console I/O standard request, and pass this block to the console device using one of the normal I/O functions. When the console device has completed the action, the device returns the message block to the port you have designated within the message itself. The function CreateStdIO() initializes the message to contain the address of the ReplyPort. Here are subroutines that uses the IOStdReq created above. Note that the IOStdReq itself contains a pointer to the device with which it is communicating so a single function can be used to communicate with multiple consoles. November 17, 1985 - 5 - /* output a single character to a specified console */ ConPutChar(request,character) struct IOStdReq *request; char character; { request->io_Command = CMD_WRITE; request->io_Data = &character; request->io_Length = 1; DoIO(request); return; } /* output a stream of known length to a console */ ConWrite(request,string,length) struct IOStdReq *request; char *string; int length; { request->io_Command = CMD_WRITE; request->io_Data = string; request->io_Length = length; DoIO(request); return; } /* output a NULL-terminated string of characters to a console */ ConPutStr(request,string) struct IOStdReq *request; char *string; { request->io_Command = CMD_WRITE; request->io_Data = string; request->io_Length = -1; /* tells console to end when it * sees a terminating zero on * the string. */ DoIO(request); return; } 1.6. CONTROL SEQUENCES FOR SCREEN OUTPUT Here is a list of the functions that the console device supports, along with the character stream that you must send to the console to produce the effect. Where the function table indicates multi- ple characters, it is more efficient to use the ConWrite() func- tion rather than ConPutChar() since it avoids the overhead of transfering the message block multiple times. The table below uses the second form of , that is, the hex value 9B, to November 17, 1985 - 6 - minimize the number of characters to be transmitted to produce a function. In the table below, if an item is enclosed in square brackets, it is an optional item and may be omitted. For example, for INSERT [N] CHARACTERS, the value for N or M is shown as optional. The console device responds to such optional items by treating the value of N as if it is not specified. The value of N or M is always a decimal number, having one or more ASCII digits to express its value. Table 1-1: Console Control Sequences COMMAND SEQUENCE OF CHARACTERS (in hexadecimal) BACKSPACE (move left one column) 08 LINE FEED (move down one text line 0A as specified by the mode function below) VERTICAL TAB (move up one text line) 0B FORM FEED (clear the console's screen) 0C CARRIAGE RETURN (move to first column) 0D SHIFT IN (undo SHIFT OUT) OE SHIFT OUT (set MSB of each character 0F before displaying) ESC (escape; can be part of the control 1B sequence introducer) CSI (control sequence introducer) ESC [ RESET TO INITIAL STATE 9B 63 INSERT [N] CHARACTERS 9B [N] 40 (Inserts one or more spaces, shifting the remainder of the line to the right.) CURSOR UP [N] CHARACTER POSITIONS 9B [N] 41 (default = 1) CURSOR DOWN [N] CHARACTER POSITIONS 9B [N] 42 (default = 1) CURSOR FORWARD [N] CHARACTER POSITIONS 9B [N] 43 (default = 1) CURSOR BACKWARD [N] CHARACTER 9B [N] 44 POSITIONS (default = 1) CURSOR NEXT LINE [N] (to column 1) 9B [N] 45 CURSOR PRECEDING LINE [N] 9B [N] 46 (to column 1) MOVE CURSOR TO ROW; COLUMN 9B [N] [3B N] 48 where N is row, M is column, and semicolon (hex 3B) must be present as a separator, or if row is left out, so the console device can tell that the number after the semicolon actually represents the column number. ERASE TO END OF DISPLAY 9B 4A ERASE TO END OF LINE 9B 4B November 17, 1985 - 7 - INSERT LINE (above the line containing 9B 4C the cursor) DELETE LINE (remove current line, move 9B 4D all lines up one position to fill gap, blank bottom line) DELETE CHARACTER [N] (that cursor is 9B [N] 50 sitting on and to the right if [N] is specified) SCROLL UP [N] LINES (Remove line(s) from 9B [N] 53 top of screen, move all other lines down, blanks [N] bottom lines). SCROLL DOWN [N] LINES (Remove line(s) 9B [N] 54 from bottom of screen, move all other lines up, blanks [N] top lines). SET MODE (cause LINEFEED to respond as 9B 32 30 68 RETURN-LINEFEED) RESET MODE (cause LINEFEED to respond 9B 32 30 6C only as LINEFEED) DEVICE STATUS REPORT (cause console to 9B 6E insert into your read-stream a CURSOR POSITION REPORT; see "Reading from the Console" for more info). SELECT GRAPHIC RENDITION See note below. [S];[F];[B] (select text style, foreground color, background color) NOTE: For SELECT GRAPHIC RENDITION, any number of parameters, in any order, are valid. They are separated by semicolons.